from PyQt5.QtGui import QFont, QPainter, QPixmap, QImage
from PyQt5.QtWidgets import QStyledItemDelegate, QStyleOptionViewItem
from PyQt5.QtCore import Qt, QByteArray, QRect, QSize


class CustomDelegate(QStyledItemDelegate):
    def __init__(self, parent=None, font=None):
        super(CustomDelegate, self).__init__(parent)
        # 设置默认字体，如果没有提供
        self.font = font or QFont("./fontFile/HarmonyOS.ttf", 12)

    def paint(self, painter: QPainter, option: QStyleOptionViewItem, index):
        # 设置字体和对齐方式
        option.font = self.font
        # 居中对齐
        option.displayAlignment = Qt.AlignCenter

        # 检查索引是否有效
        if not index.isValid():
            print('索引无效')
            # 如果索引无效，调用父类的paint方法绘制
            return super().paint(painter, option, index)

        # 首先调用父类的paint方法来绘制背景和文本
        super().paint(painter, option, index)

        # 图片存放在第6列
        if index.column() == 6:
            # 从模型中获取用户自定义角色的数据，图片数据存储在 UserRole + 1
            image_data = index.model().data(index, Qt.UserRole + 1)
            # 检查数据是否为QByteArray类型
            if isinstance(image_data, QByteArray):
                # 创建一个QImage对象
                image = QImage()
                # 从字节数据中加载图片
                success = image.loadFromData(image_data)
                # 检查图片是否成功加载
                if success:
                    # QImage -> QPixmap
                    pixmap = QPixmap.fromImage(image)

                    # 固定单元格的宽度和高度
                    cell_width = 160
                    cell_height = 120

                    # 根据单元格大小按比例缩放图片，保持宽高比
                    scaled_pixmap = pixmap.scaled(cell_width, cell_height,
                                                  Qt.KeepAspectRatio, Qt.SmoothTransformation)

                    # 计算图片在单元格中的位置，使其居中
                    x = int(option.rect.x() + (cell_width - scaled_pixmap.width()) / 2)
                    y = int(option.rect.y() + (cell_height - scaled_pixmap.height()) / 2)

                    # 绘制图片
                    painter.drawPixmap(QRect(x, y, scaled_pixmap.width(), scaled_pixmap.height()), scaled_pixmap)

    def sizeHint(self, option, index):
        """
        写父类的sizeHint方法，用于返回单元格的大小提示。
        :param option:
        :param index:
        :return:
        """
        # 定义各列的宽度
        column_widths = {
            0: 100,  # 第一列宽度为100
            1: 100,  # 第二列宽度为100
            2: 100,  # 第三列宽度为100
            3: 100,  # 第四列宽度为100
            4: 150,  # 第五列宽度为155
            5: 150,  # 第六列宽度为160
            6: 160,  # 第七列宽度为160
        }
        # 高度固定为120
        height = 120

        # 根据列索引返回对应宽度，如果不是指定的列则使用默认宽度
        width = column_widths.get(index.column(), 100)  # 默认宽度为100

        return QSize(width, height)